package com.a01_2021.thousandstimes.utils;

import com.a01_2021.thousandstimes.instance.entity.Vote;

import java.time.LocalDate;
import java.util.ArrayList;
import java.util.Collections;
import java.util.List;
import java.util.Random;

/**
 * @Author E1xP@foxmail.com
 * @Version 1.0
 * @PACKAGE_NAME com.a01_2021.thousandstimes.utils
 * @CLASS_NAME Utils
 * @Description TODO Utils工具类
 * @Date 2021/3/28 上午 10:35
 **/
public class Utils {

    /**
     * 生成一对多的不重复评价映射
     * 差额评价，且不两人间循环评价(需要总人数大于两倍评价窗口大小时
     *
     * @param interpersonalCount 评价窗口大小
     * @param list               人员列表
     * @param date               评价月时间
     * @return Vote列表
     */
    public static List<Vote> getVoteMapping(int interpersonalCount, List<Long> list, LocalDate date) {
        Collections.shuffle(list);//打乱员工顺序
        ArrayList<Vote> resultList = new ArrayList<>();
        if (list.size() <= interpersonalCount + 1) {
            //此时全评价
            for (long item : list) {
                for (long item1 : list) {
                    if (item != item1) {
                        resultList.add(new Vote(null, item, item1, null, date, null));
                    }
                }
            }
        } else {
            /*
            此时差额评价
            差额评价打乱员工顺序
            评价人数作为评价窗口
            以评价窗口内人员作为被评价的人，远处随机偏移量的人作为评价人
            两者间以随机获得的固定偏移量作为距离
            评价窗口随着评价人滑动
             */
            Random random = new Random(System.currentTimeMillis());
            int differCount = list.size() - interpersonalCount;//差额幅度=总人数-窗口大小
            int offset = random.nextInt(differCount) - 1;//获取评价人与评价窗口的偏移量(0~差额人数-1)
            int windowsStart = 0;//窗口开始下标
            for (int i = windowsStart; i < list.size(); i++) {
                //评价窗口滑动
                for (int j = i; j < interpersonalCount + i; j++) {
                    //设被评价人与评价人
                    resultList.add(new Vote(null, list.get((j) % list.size()), list.get((i + offset + interpersonalCount) % list.size()), null, date, null));
                }
            }
        }
        return resultList;
    }
}
